/*
 * Copyright (C) 2020 The LINN Authors
 *
 * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except
 * in compliance with the License. You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software distributed under the License
 * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
 * or implied. See the License for the specific language governing permissions and limitations under
 * the License.
 */
package com.juqimiao.linn.context;

import java.security.InvalidParameterException;

/**
 * 表示一个业务扩展点的类。
 *
 * <p>
 *     一个业务扩展点，定义了不同的租户可能执行不同的User Case甚至涉及不同场景点。
 *     通常通过一下方式提供扩展点定义。
 *     businessId = "businessId"；
 *     或者
 *     businessId = "businessId"；
 *     userCase = "userCase"；
 *     或者
 *     businessId = "businessId"；
 *     userCase = "userCase"；
 *     scenario = "scenario"；
 *     更多信息请参见 Extension.
 * </p>
 *
 * @author Collin Cai
 */
public class BusinessPoint {

    private static final String ARGU_ERROR = "If userCase is null, the scenario must be null.";
    /**
     * Todo: 从配置文件中读取业务前缀
     */
    private static final String BUSINESS_VALUE_PREFIX = "empty-";
    public static final String DEFAULT_BUSINESS_ID = BUSINESS_VALUE_PREFIX + "bid";
    public static final String DEFAULT_USER_CASE = BUSINESS_VALUE_PREFIX + "uc";
    public static final String DEFAULT_SCENARIO = BUSINESS_VALUE_PREFIX + "bs";
    public static final String SEPARATOR = "$";

    private String businessId = "";
    private String userCase = "";
    private String scenario = "";

    private BusinessPoint(){}

    /**
     * 获取唯一标识。它由 businessId & userCase & scenario组成的字符串表示。
     *
     * @return 一个唯一标识。
     */
    public String getUniqueId() {
        String result = "";

        if(businessId != null && !"".equals(businessId)){
            result += this.businessId;
        }
        if(userCase != null && !"".equals(userCase)){
            result +=  "".equals(result) ? userCase : SEPARATOR + userCase;
        }

        if(scenario != null && !"".equals(scenario)){
            result +=  "".equals(result) ? scenario : SEPARATOR + scenario;
        }

        return result;
    }

    /**
     * 构造器
     *
     * @param businessId    业务识别码
     * @param userCase      用户故事
     * @param scenario      场景
     *
     * @return 一个{@link BusinessPoint} 对象。
     */
    public static BusinessPoint valueOf(String businessId, String userCase, String scenario) {
        if(isNull(userCase)) {
            if(!isNull(scenario)) {
                throw new InvalidParameterException(ARGU_ERROR);
            }
        }
        BusinessPoint businessPoint = new BusinessPoint();
        businessPoint.businessId = businessId;
        businessPoint.userCase = userCase;
        businessPoint.scenario = scenario;
        return businessPoint;
    }

    /**
     * 转化获得 {@link BusinessPoint} 对象。
     *
     * @param businessId    业务识别码
     *
     * @return 一个{@link BusinessPoint} 对象。
     */
    public static BusinessPoint valueOf(String businessId) {
        return BusinessPoint.valueOf(businessId, null, null);
    }

    /**
     * 转化获得 {@link BusinessPoint} 对象。
     *
     * @param userCase 用户故事
     * @param scenario 场景
     *
     * @return 一个{@link BusinessPoint} 对象。
     */
    public static BusinessPoint valueOf(String userCase, String scenario) {
        return BusinessPoint.valueOf(DEFAULT_BUSINESS_ID, userCase, scenario);
    }

    /**
     * 构建一个默认的 {@link BusinessPoint} 对象。默认对象包含系统预设的 businessId、userCase 和 scenario。
     *
     * @return 一个{@link BusinessPoint} 对象。
     */
    public static BusinessPoint createDefault() {
        return BusinessPoint.valueOf(DEFAULT_BUSINESS_ID, null, null);
    }

    private static Boolean isNull(String value) {
        return (value == null || "".equals(value));
    }
}
